classdef TestDotsComputableFunction < dotsTestCase
    
    properties
        cm;
    end
    
    methods
        function self = TestDotsComputableFunction(name)
            self = self@dotsTestCase(name);
        end
        
        function setUp(self)
            self.setUp@dotsTestCase;
            
            topsDataLog.flushAllData;
            dotsTheComputablesManager.reset;
            self.cm = dotsTheComputablesManager.theObject;
        end
        
        function tearDown(self)
            topsDataLog.flushAllData;
            %dotsTheComputablesManager.reset;
            self.tearDown@dotsTestCase;
        end
        
        function testComputeResult(self)
            computable = self.cm.newObject('dotsComputableFunction');
            fun = @(input)numel(input);
            computable.computeFunction = fun;
            
            input = 1:10;
            computable.computeInputs = {input};
            expectedResult = numel(input);
            result = computable.compute;
            assertEqual(result, expectedResult, ...
                'compute() result should match expected result')
            assertEqual(computable.computeResult, expectedResult, ...
                'computeResult property should match expected result')
            
            input = 1:20;
            computable.computeInputs = {input};
            expectedResult = numel(input);
            self.cm.callObjectMethod(computable, 'compute');
            result = self.cm.getObjectProperty(computable, 'computeResult');
            assertEqual(result, expectedResult, ...
                'manager compute-then-get result should match expected result')

            input = 1:30;
            computable.computeInputs = {input};
            expectedResult = numel(input);
            result = self.cm.mayComputeComputable(computable);
            assertEqual(result, expectedResult, ...
                'manager compute-with-return result should match expected result')
        end
        
        function testRecompute(self)
            computable = self.cm.newObject('dotsComputableFunction');
            fun = @(input)numel(input);
            computable.computeFunction = fun;
            
            computable.recomputeInterval = 0;
            computable.prepareToCompute;
            
            input = 1:10;
            computable.computeInputs = {input};
            expectedResult = numel(input);
            computable.mayComputeNow(0);
            assertEqual(computable.computeResult, expectedResult, ...
                'first re-compute() result should match computeResult property')
            
            
            input = 1:100;
            computable.computeInputs = {input};
            expectedResult = numel(input);
            computable.mayComputeNow(0);
            assertEqual(computable.computeResult, expectedResult, ...
                're-re-compute() result should match computeResult property')
        end
    end
end